package com.app.oasystem.timer;

import com.app.oasystem.entity.Record;
import com.app.oasystem.entity.User;
import com.app.oasystem.mapper.RecordMapper;
import com.app.oasystem.mapper.UserMapper;
import com.app.oasystem.service.RecordService;
import com.app.oasystem.service.impl.UserServiceImpl;
import com.app.oasystem.utils.MyCollectionUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 打卡的定时任务
 * 打了上班卡。没打下班卡的，自动为6点下班
 * 没打上班卡（也就意味着没打下班卡），上下班时间定为昨天的晚11点，旷班处理
 *
 * @author zhangbaobing
 * @Description TODO
 * @data 2021/05/17
 */
@Component
@Slf4j
public class HitCardTimer {

    @Resource
    UserServiceImpl userService;

    @Resource
    RecordService recordService;

    /**
     * 0 0 1 * * ?   即为每日凌晨1点启动定时任务
     * 报错的意思是，只能是6位的，而我写了7位，
     * 查了资料后，有网友说，最后一位表示的年，
     * 1099~2099年，可以省略不写，就可以啦
     */
    @Scheduled(cron = "0 0 1 * * ?")
    @Transactional(rollbackFor = Exception.class)
    public void execute() {
        log.info("---------打卡定时器开始----------");
        //判断当前系统是否有成员
        List<User> userList = userService.getUserList();
        if (null != userList) {
            //获取当前系统所有用户的id列表
            List<Integer> userIds = userList.stream().map(User::getId).collect(Collectors.toList());
            //获取当前系统所有当天打卡的信息
            List<Record> records = recordService.getLikeCurrentDayRecord();
            //获取所有已经打过卡的人员列表
            List<Integer> recordIds = records.stream().map(Record::getUid).collect(Collectors.toList());
            //对比系统用户，看哪些人员未曾打卡
            List<Integer> diffrent = MyCollectionUtil.getDiffrent(userIds, recordIds);
            //未打卡的人为旷班，时间定为昨天的晚11点
            long absenteeismTimer = System.currentTimeMillis() - 2 * 60 * 60 * 1000;
            common(diffrent, absenteeismTimer);
            //打了上班卡。没打下班卡的，自动为6点下班
            List<Integer> noRecordEndTimes = records.stream().filter(r -> null == r.getEndtime()).collect(Collectors.toList()).stream().map(Record::getUid).collect(Collectors.toList());
            long noTimer = System.currentTimeMillis() - 7 * 60 * 60 * 1000;
            common(noRecordEndTimes, noTimer);

        }


        log.info("---------打卡定时器结束----------");
    }

    private synchronized void common(List<Integer> userIds, long timer) {
        for (Integer userId : userIds) {
            Record record = new Record();
            record.setUid(userId);
            record.setStatus(0);
            User userInfo = userService.getUserInfo(userId);
            record.setUsername(userInfo.getUsername());
            record.setPhone(userInfo.getPhone());
            record.setBegintime(new Date(timer));
            record.setEndtime(new Date(timer));
            recordService.insertRecord(record);
        }
    }
}
